package com.trailer.base.base

import android.content.Context
import android.content.pm.ActivityInfo
import android.graphics.Color
import android.os.Bundle
import android.text.TextUtils
import android.view.View
import android.view.ViewGroup
import android.widget.EditText
import android.widget.LinearLayout
import androidx.annotation.ArrayRes
import androidx.annotation.ColorRes
import androidx.annotation.IdRes
import androidx.annotation.StringRes
import androidx.constraintlayout.widget.ConstraintLayout
import androidx.constraintlayout.widget.ConstraintSet
import androidx.databinding.ViewDataBinding
import androidx.lifecycle.ViewModelProvider
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout
import com.githang.statusbar.StatusBarCompat
import com.hwangjr.rxbus.RxBus
import com.kingja.loadsir.callback.Callback.OnReloadListener
import com.kingja.loadsir.core.LoadService
import com.kingja.loadsir.core.LoadSir
import com.qmuiteam.qmui.util.QMUIStatusBarHelper
import com.trello.rxlifecycle2.components.support.RxAppCompatActivity
import com.trailer.base.BR
import com.trailer.base.R
import com.trailer.base.inter.IUser
import com.trailer.base.utils.Toasts
import com.trailer.base.utils.UiSwitch
import com.trailer.base.view.BView
import com.trailer.base.widget.TitleBar
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.SupervisorJob
import kotlinx.coroutines.cancelChildren
import kotlin.coroutines.CoroutineContext

abstract class BActivity<VM : BViewModel<*>, B : ViewDataBinding> : RxAppCompatActivity(), BView, OnReloadListener, TitleBar.DataSource, CoroutineScope {

    private val job = SupervisorJob()

    override val coroutineContext: CoroutineContext
        get() = Dispatchers.Main + job


    override fun coroutine(): CoroutineScope {
        return this
    }

    protected lateinit var vm: VM
    override var loadService: LoadService<*>? = null
    protected lateinit var binding: B
    private var swipeRefreshLayout: SwipeRefreshLayout? = null
    private var imgLeft: View? = null
    private var loginStatus = 0
    fun titleBar(): TitleBar? {
        return titleBar
    }

    private var titleBar: TitleBar? = null

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        try {
            //设置坚屏 一定要放到try catch里面，否则会崩溃
            setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT)
        } catch (e: Exception) {
        }

        binding = binding()
        binding.lifecycleOwner = this

        vm = ViewModelProvider(this)[vmClass()]
        vm.attachView(this)
        vm.init()
        __before()

        binding.setVariable(BR.vm, vm)
        val rootView = binding.root as ViewGroup
        swipeRefreshLayout = rootView.findViewById(R.id.refresh_layout)
        if (swipeRefreshLayout != null) {
            setSwipeRefreshLayoutStyle()
        }
        var contentView: View? = null
        if (provideContainerId() != -1) {
            contentView = rootView.findViewById(provideContainerId())
        }
        if (title() != null) {
            titleBar = TitleBar(this, this)
            if (rootView is LinearLayout) {
                rootView.addView(titleBar, 0)
            } else if (rootView is ConstraintLayout) {
                rootView.addView(titleBar, 0)
                titleBar!!.id = View.generateViewId()
                val set = ConstraintSet()
                set.clone(rootView)
                set.connect(titleBar!!.id, ConstraintSet.START, ConstraintSet.PARENT_ID, ConstraintSet.START)
//                set.connect(titleBar!!.id, ConstraintSet.TOP, ConstraintSet.PARENT_ID, ConstraintSet.TOP, QMUIStatusBarHelper.getStatusbarHeight(context()))
                set.applyTo(rootView)
            }
        }

        setContentView(rootView)
        setStatusBar()
        register()
        loadService = if (contentView != null) {
            LoadSir.getDefault().register(contentView, this)
        } else {
            LoadSir.getDefault().register(this, this)
        }
        initView(rootView)
        listeners()
        customizeEmptyView()
        init(savedInstanceState)
        onRefresh()

        initObserver();
    }

    private fun initObserver() {
        vm.refreshing.observe(this) { refreshing ->
            refreshing(refreshing)
            if (refreshing) {
                onRefresh()
            }
        }
    }

    protected open fun vmClass(): Class<VM> {
        return BViewModel::class.java as Class<VM>
    }

    /**
     * oncreate 前置操作
     */
    open fun __before() {}

    override fun setStatusBar() = if (transluent()) {
        QMUIStatusBarHelper.translucent(this)
    } else {
        StatusBarCompat.setStatusBarColor(this, Color.parseColor("#ffffff"))

//        StatusBarUtil.setColor(this, resources.getColor(R.color.white), 1)
    }

    override fun initView(view: View?) {
        imgLeft = findViewById(R.id.img_back)
    }

    /**
     * 初始化
     *
     * @param savedInstanceState
     */
    protected open fun init(savedInstanceState: Bundle?) {}
    override fun customizeEmptyView() {}
    fun setTitle(title: String?) {
        runOnUiThread {
            if (titleBar != null) {
                if (!TextUtils.isEmpty(title)) {
                    titleBar?.tv_title_bottom?.visibility = View.VISIBLE
                    titleBar?.tv_title_bottom?.text = title
                } else {
                    titleBar?.tv_title_bottom?.visibility = View.GONE
                }
            }
        }
    }

    /**
     * 初始化Listeners
     */
    override fun listeners() {
        if (imgLeft != null) {
            imgLeft!!.setOnClickListener { v: View? -> finishActivity() }
        }
    }

    protected abstract fun binding(): B


    override fun context(): Context {
        return this
    }

    override fun onDestroy() {
        super.onDestroy()
        coroutineContext.cancelChildren()
        unRegister()
    }


    override fun onReload(v: View?) {
        if (needLogin() && user() == null) {
            toLogin()
            return
        }
        vm.firstReq()
    }

    override fun finishActivity() {
        onBackPressed()
        if (exitFromTopAnim()) {
            overridePendingTransition(R.anim.acitivity_no_amination, R.anim.acitivity_hide_from_top_amination)
        }
    }

    override fun finish() {
        super.finish()
    }

    override fun toast(msg: String?) {
        if (!TextUtils.isEmpty(msg)) {
            runOnUi(Runnable { Toasts.toast(context(), msg) })
        }
    }

    override fun toast(@StringRes msgID: Int) {
        toast(resources.getString(msgID))
    }

    override fun getEdtStr(editText: EditText?): String? {
        return editText!!.text.toString().trim { it <= ' ' }
    }

    override fun getStr(stringId: Int): String? {
        return getString(stringId)
    }

    override fun getStrArr(@ArrayRes strArrId: Int): Array<String?>? {
        return resources.getStringArray(strArrId)
    }

    override fun processCodeOffline() {

    }

    override fun toLogin() {
        loginStatus = TO_LOGIN
    }

    override fun onResume() {
        super.onResume()

        if (loginStatus == TO_LOGIN) {
            onRefresh()
            loginStatus = 0
        }
    }

    override fun needLogin(): Boolean {
        return false
    }

    override fun title(): String? {
        return ""
    }

    override fun backable(): Boolean {
        return true
    }

    override fun transluent(): Boolean {
        return false
    }

    @ColorRes
    override fun titleColor(): Int {
        return R.color.white
    }

    @ColorRes
    override fun rightTextColor(): Int {
        return R.color.white
    }


    override fun titleSize(): Int {
        return 17
    }

    override val isRxbus: Boolean
        get() = false

    override fun register() {
        if (isRxbus) RxBus.get().register(this)
    }

    override fun unRegister() {
        if (isRxbus) RxBus.get().unregister(this)
    }

    override fun view(): BView? {
        return this
    }

    override fun runOnUi(runnable: Runnable?) {
        runOnUiThread(runnable)
    }

    override fun <T> single(clazz: Class<T>?) {
        UiSwitch.single(context(), clazz)
    }

    override fun <T> bundle(clazz: Class<T>?, bundle: Bundle?) {
        UiSwitch.bundle(context(), clazz, bundle)
    }


    override fun onRefresh() {
        onReload(null)
    }

    override fun refreshing(refreshing: Boolean) {
        if (swipeRefreshLayout != null) {
            swipeRefreshLayout!!.isRefreshing = refreshing
        }
    }

    override val isNeedRefresh: Boolean
        get() = true


    private fun setSwipeRefreshLayoutStyle() {
        /*下拉刷新设置*/
        if (swipeRefreshLayout != null) {
            swipeRefreshLayout!!.setOnRefreshListener { onRefresh() }
            swipeRefreshLayout!!.setColorSchemeResources(R.color.refresh_colorPrimary, R.color.refresh_colorAccent, R.color.refresh_colorPrimaryDark)
            swipeRefreshLayout!!.setOnRefreshListener { onRefresh() }
            swipeRefreshLayout!!.isEnabled = isNeedRefresh
        }
    }

    @IdRes
    override fun provideContainerId(): Int {
        return R.id.refresh_layout
    }

    override fun exitFromTopAnim(): Boolean {
        return false
    }

    override fun user(): IUser? {
        return null
    }

    companion object {
        const val TO_LOGIN = 1
    }

}
